package validation;

import coma2012.Communicator;
import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.logging.Level;
import java.util.logging.Logger;
import sun.scheduler.core.*;
import sun.scheduler.core.job.Job;
import sun.scheduler.core.leveling.LevelingAlgorithm;
import sun.scheduler.core.resource.Resource;
import sun.scheduler.core.scheduling.ResourceScheduler;
import sun.scheduler.io.ScheduleReader;
import sun.scheduler.io.ScheduleWriter;

/**
 * A simple class showing how to read input/output files from hard drive and
 * submit the data to the validator class.
 */
public class Test
{

    public static void main(String[] args)
    {
        String jobFile, ressourceFile;
        jobFile = "t1_5jobs.csv";
        ressourceFile = "t1_5res.csv";
        
        jobFile = "prA_jobs.csv";
        ressourceFile = "prA_resources.csv";
//        test(-1, jobFile, ressourceFile);
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(44, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
        test(100, jobFile, ressourceFile);

//        jobFile = "prB_jobs.csv";
//        ressourceFile = "prB_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(98, jobFile, ressourceFile);
//    
//        jobFile = "prB_jobs.csv";
//        ressourceFile = "prB_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//        
//        jobFile = "prC_jobs.csv";
//        ressourceFile = "prC_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prE_jobs.csv";
//        ressourceFile = "prC_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//        
//        jobFile = "prF_jobs.csv";
//        ressourceFile = "prC_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//        
//        jobFile = "prC_jobs.csv";
//        ressourceFile = "prC_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prD_jobs.csv";
//        ressourceFile = "prD_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prE_jobs.csv";
//        ressourceFile = "prE_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prF_jobs.csv";
//        ressourceFile = "prF_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prG_jobs.csv";
//        ressourceFile = "prG_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prH_jobs.csv";
//        ressourceFile = "prH_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
//    
//        jobFile = "prI_jobs.csv";
//        ressourceFile = "prI_resources.csv";
//        test(1, jobFile, ressourceFile);
//        test(5, jobFile, ressourceFile);
//        test(10, jobFile, ressourceFile);
//        test(15, jobFile, ressourceFile);
//        test(20, jobFile, ressourceFile);
//        test(30, jobFile, ressourceFile);
//        test(40, jobFile, ressourceFile);
//        test(80, jobFile, ressourceFile);
//        test(100, jobFile, ressourceFile);
    
    }
    
    public static void test(int steps, String jobFile, String ressourceFile)
    {   
        ArrayList<Resource> resources = null;
        ArrayList<Job> jobs = null;
        try
        {
            resources = ScheduleReader.readResourcesFromFile(ressourceFile);
            jobs = ScheduleReader.readJobsFromFile(resources, jobFile);
            
        }
        catch (ParseException ex)
        {
            ex.printStackTrace();
        }
        
        ScheduleGraph sGraph = Main.getScheduleGraph(steps, jobs);
        
//        LevelingAlgorithm lvlalg = new LevelingAlgorithm(sGraph, sGraph.getResourceProfiles());
//        lvlalg.run();
        
        ScheduleWriter.writeResourceFile("temp_res_out.csv", sGraph.getResourceProfiles().asList());
        ScheduleWriter.writeProcessFile("temp_jobs_out.csv", jobs, ScheduleReader.getStartDate(), Job.CurveState.Scheduling);

        String instance = jobFile.split("_")[0];
        /*
         * This tries to submit computed results for the file t1_28. The name of
         * the instance is submitted as third parameter, it is not needed to
         * provide the input itself. Using this method, the results are not only
         * verified, but also added to the ranking on the website. The first two
         * parameter are the number of the company and the corresponding
         * password that you should have received by other means. The last two
         * parameters have to contain the file content as string, the job output
         * is the fourth parameter, the ressource output the last parameter.
         */
        try
        {
            String feedback = Communicator.sendOutputToValidator(15, "DQCabHaJ", instance, readFile("temp_jobs_out.csv"), readFile("temp_res_out.csv"));
            System.out.println(feedback);
            System.out.println(" > tested " + instance + ": time " + Main.getTotalTime(sGraph) + ", cost " + Main.getTotalCost(sGraph));
        }
        catch (Exception e)
        {
            // TODO: handle exception
        }

        /*
         * This variant submits the result for an input that is also to be
         * submitted. Note that using this variant, the results are only
         * verified and not used for the ranking. The first two parameters
         * remain the same, the company number and the password. The next two
         * parameters specifiy the instance used to compute the output. The
         * strings again have to contain the file content, first the job input
         * and then the ressource input. The last parameters specify the
         * computed result, the job and ressoruce output.
         */
        try
        {
//            String feedback = Communicator.sendOutputToValidator(15, "DQCabHaJ", readFile(jobFile), readFile(ressourceFile), readFile("t1_28jobs_out.csv"), readFile("t1_28res_out.csv"));
//            System.out.println(feedback);
//            System.out.println(" > tested " + instance + ": time " + Main.getTotalTime(sGraph) + ", cost " + Main.getTotalCost(sGraph));
        }
        catch (Exception e)
        {
            // TODO: handle exception
        }

    }

    /**
     * Reads a file from hard drive and returns the content as string.
     *
     * @param fileName the file that is read
     * @return the content of the file as string
     */
    public static String readFile(String fileName)
    {
        File file = new File(fileName);
        StringBuilder outputStringBuilder = new StringBuilder((int) file.length() * 2);

        try
        {
            FileInputStream fis = new FileInputStream(fileName);
            BufferedInputStream bis = new BufferedInputStream(fis);

            while (true)
            {
                int c = bis.read();
                if (c == -1)
                    break;
                outputStringBuilder.append((char) c);
            }

            bis.close();
            fis.close();
        }
        catch (Exception ex)
        {
            System.out.println(ex.toString());
            ex.printStackTrace(System.err);
        }
        return outputStringBuilder.toString();
    }

}
